import os
import sys
sys.path.append("..")   #也可以这样
import time
from config import kLocUserImagesPath, kSourceVideosFrame, kUserSwapperFaceFrames, kFontPath
from utils.image_utils import process_user_image
from utils.video_utils import split_video_into_frames, 加水印
from loguru import logger
from utils import face_swapper_process
from utils.cloud_utils import upload_file_to_aliyun, transform_path, upload_file_to_qiniu
from tybase.tools.image_utils import url_to_md5
from tybase.tools.image_utils import delete_file_or_directory
from utils.video_utils import synthesize_video
from celerytask import app

preprocess_source_images_v2 = app.tasks['celerytask.tasks.preprocess_source_images_v2']  # 人脸验证的api流程
# 把这整个包装成一个task,然后直接发送任务就可以了

# 视频换脸流程
def 多人_视频_换脸(requests_data):
    # 传入的数据其实是这样的:
    '''
    requests_data = {
        "target_video":"https://ty-aihuanlian.oss-cn-shanghai.aliyuncs.com/test/RPReplay_Final1699878287.mov",
        "face_data":[
            {
                "target_face_url":"http://ty-huanlian.oss-cn-shanghai.aliyuncs.com/swap_face%2F202311%2Fbest_face_0_1700020151_output_frame_4.jpg",
                "user_face_urls":["http://usfile.chaotuapp.com/uploads/android/user/1699935515321.jpg"]
            },
            {
                "target_face_url":"http://ty-huanlian.oss-cn-shanghai.aliyuncs.com/swap_face%2F202311%2Fbest_face_1_1700020151_output_frame_6.jpg",
                "user_face_urls":["https://ty-aihuanlian.oss-cn-shanghai.aliyuncs.com/test/IMG_2760.jpg"]
            }
        
        ]
    }
    '''
    帧数 = requests_data.get("frames", 15)  # 如果没有就15帧
    水印 = requests_data.get("shuiyin", True)  # 如果没有就15帧
    oss_name = requests_data.get("oss_name", "ali")  # 如果没有就15帧

    try:
        # 这里要进行拆分来处理!
        frame_name = "frame_%04d.jpg"
        # 这部分的逻辑也可以改,直接改成可以加水印的
        video_loc_frame_path = split_video_into_frames(requests_data["target_video"], kSourceVideosFrame=kSourceVideosFrame,
                                                       frames=帧数, frame_name=frame_name)   
        
        logger.info("视频分割完毕..,开始解析人脸向量对")        
        # TODO: 这里有个异步任务
        face_pairs_list = preprocess_source_images_v2.delay(requests_data["face_data"]).get(timeout=30)
        logger.info("人脸向量对分析完毕,开始进行多线程换脸")
        # 主线程,开始发布很多任务
        
        # 先把视频的路径先拼凑完毕
        full_video_paths_list = []
        for i in os.listdir(video_loc_frame_path):
            if ".aac" not in i and ".jpg" in i:
                #看了是有正常在换脸的,但是为什么没合成?
                full_video_paths_list.append(os.path.join(video_loc_frame_path, i))
        # 这个函数里面还有一系列异步任务
        output_directory_name = face_swapper_process.process_images_many_face(face_pairs_list, full_video_paths_list,
                                                                    f"{video_loc_frame_path}_{int(time.time())}")
        output_path = kUserSwapperFaceFrames + f"/{url_to_md5(requests_data['target_video']).split('.')[0]}_{int(time.time())}.mp4"
        logger.info("换脸完毕,合成视频路径:{}".format(output_path))
    
        # # 对视频进行合成!
        synthesize_video(image_directory=output_directory_name,
                         audio_path=video_loc_frame_path + "/audio.aac",
                         output_path=output_path,
                         frame_rate=帧数,
                         crf=22,
                         frame_name=frame_name,
                         )
        
        logger.info("换脸完毕,合成视频路径:{}".format(output_path))
        print("要不要加水印?")
        if 水印:
            加水印(output_path, fontfile_path=kFontPath)

        aliyun_file_path = transform_path(output_path)

        # # 把链接上传到阿里云,构建好完整的路径

        if oss_name == "qiniu":
            cloud_url = res_url = upload_file_to_qiniu(aliyun_file_path, output_path)
        else:
            cloud_url = upload_file_to_aliyun(
                aliyun_file_path, output_path)
            res_url = cloud_url.split('aliyuncs.com/')[-1]
            # 这里执行你的实际工作
        return {
            "video_loc_frame_path": video_loc_frame_path,
            "output_directory_name": output_directory_name,
            "output_path": output_path,
            "aliyun_file_path": cloud_url,
            "ty_path": res_url,
            "verify_face": True,
            "error_message": ""
        }


    except Exception as e:
        return {
            "video_loc_frame_path": video_loc_frame_path,
            "output_directory_name": output_directory_name,
            "output_path": output_path,
            "aliyun_file_path": cloud_url,
            "ty_path": res_url,
            "verify_face": True,
            "error_message": e[:200]
        }
    finally:
        try:
            delete_file_or_directory(output_directory_name)
            delete_file_or_directory(output_path)
            # 用户图片不用删除,因为是直接读取image的对象的!
            delete_file_or_directory(video_loc_frame_path)
        except:
            pass


if __name__ == '__main__':
    from tybase.tools.Task import TaskRunner
    # 可以把参数全部包装在这里,也比较简单!
    requests_data = {
        "target_video":"https://ty-aihuanlian.oss-cn-shanghai.aliyuncs.com/test/RPReplay_Final1699878287.mov",
        "face_data":[
            {
                "target_face_url":"http://ty-huanlian.oss-cn-shanghai.aliyuncs.com/swap_face%2F202311%2Fbest_face_0_1700020151_output_frame_4.jpg",
                "user_face_urls":["http://oss.ubookapp.com/outputs/test/WX20231115-121354@2x.png"]
            },
            {
                "target_face_url":"http://ty-huanlian.oss-cn-shanghai.aliyuncs.com/swap_face%2F202311%2Fbest_face_1_1700020151_output_frame_6.jpg",
                "user_face_urls":["https://ty-aihuanlian.oss-cn-shanghai.aliyuncs.com/test/IMG_2760.jpg"]
            }
        
        ],
        "帧数":15,
        "水印":True,
        "oss_name":"ali"
    }
    
    # 最终传递的
    print (多人_视频_换脸(requests_data))
    # 创建后台任务
    # task = TaskRunner.Task(视频_换脸, {'param1': 'value1', 'param2': 'value2'}, callback=notify)
    
    

